package com.barney.support.util;

/**
 * 문자열 유틸리티
 */
public class StringUtils {

	/**
	 * <p>
	 * Converts a string in "camel case" to its underscored, lower-case
	 * equivalent, e.g. "minimumFieldWidth" => "minimum_field_width".
	 * </p>
	 * <p>
	 * The algorithm determines each character's type as one of
	 * lower-case-character, upper-case-character, digit or other (punctuation, ...).
	 * An underscore is inserted in between each change of character type,
	 * except for the change from upper- to lower-case characters.
	 * </p>
	 *
	 * @see <a href="http://groups.google.com/group/mybatis-user/msg/7ea4b4ba34243808">이 소스 출처</a>
	 * @param text a text in camel case form, e.g. "columnKey2value"
	 * @return the lower-cased, underscored form, e.g. "column_key_2_value"
	 */
	public static String camelCase2underScore(String text) {
		StringBuilder builder = new StringBuilder(text.length() + 5);
		CharType lastCharType = null;
		for (int i = 0, count = text.length(); i < count; ++i) {
			char c = text.charAt(i);
			CharType charType = CharType.get(c);
			// noinspection OverlyComplexBooleanExpression
			if (lastCharType != null && lastCharType != charType
					&& !(lastCharType == CharType.UPPER && charType == CharType.LOWER)) {
				builder.append('_');
			}
			builder.append(Character.toLowerCase(c));
			lastCharType = charType;
		}
		return builder.toString();
	}

	/**
	 * Represents the classification of a character into lower-case-character,
	 * upper-case-character, digit or other. Uses the unicode character types
	 * (so that for example "ä" counts as a lower-case-character).
	 *
	 * @see <a href="http://groups.google.com/group/mybatis-user/msg/7ea4b4ba34243808">이 소스 출처</a>
	 */
	private enum CharType {
		LOWER, UPPER, DIGIT, OTHER;

		public static CharType get(char c) {
			if (Character.isLowerCase(c)) {
				return LOWER;
			}
			if (Character.isUpperCase(c)) {
				return UPPER;
			}
			if (Character.isDigit(c)) {
				return DIGIT;
			}
			return OTHER;
		}
	}
}
